import weakref

special_attrs = ['__abs__', '__add__', '__and__', '__call__', '__cmp__', 
    '__contains__', '__delitem__', '__delslice__', '__div__', '__divmod__', 
    '__eq__', '__float__', '__floordiv__', '__ge__', '__getitem__', 
    '__getslice__', '__gt__', '__hash__', '__hex__', '__iadd__', '__iand__', 
    '__idiv__', '__ifloordiv__', '__ilshift__', '__imod__', '__imul__', 
    '__index__', '__int__', '__invert__', '__ior__', '__ipow__', '__irshift__',
    '__isub__', '__iter__', '__itruediv__', '__ixor__', '__le__', '__len__', 
    '__long__', '__lshift__', '__lt__', '__mod__', '__mul__', '__ne__', 
    '__neg__', '__nonzero__', '__oct__', '__or__', '__pos__', '__pow__', 
    '__radd__', '__rand__', '__rdiv__', '__rdivmod__', '__reduce__', 
    '__reduce_ex__', '__repr__', '__rfloordiv__', '__rlshift__', '__rmod__', 
    '__rmul__', '__ror__', '__rpow__', '__rrshift__', '__rshift__', '__rsub__',
    '__rtruediv__', '__rxor__', '__setitem__', '__setslice__', '__str__', 
    '__sub__', '__truediv__', '__xor__', 'next']


class Proxy(object):
    __slots__ = ["__weakref__", "__target__"]
    def __init__(self, obj):
        object.__setattr__(self, "__target__", obj)
    def __getattribute__(self, name):
        return getattr(object.__getattribute__(self, "__target__"), name)
    def __delattr__(self, name):
        delattr(object.__getattribute__(self, "__target__"), name)
    def __setattr__(self, name, value):
        setattr(object.__getattribute__(self, "__target__"), name, value)
    for _name in special_attrs:
        exec "%s = lambda _self, *_a, **_k: _self.%s(*_a, **_k)" % (_name, _name)
    del _name


class Attribute(object):
    __slots__ = ["proxies"]
    def __init__(self):
        self.proxies = weakref.WeakKeyDictionary()
    def __get__(self, inst, cls):
        if inst is None:
            return self
        if inst not in self.proxies:
            raise AttributeError("not set")
        return self.proxies[inst]
    def __delete__(self, inst):
        if inst not in self.proxies:
            raise AttributeError("not set")
        del self.proxies[inst]
    def __set__(self, inst, value):
        if isinstance(value, Proxy):
            self.proxies[inst] = Proxy
        else:
            self.proxies[inst] = Proxy(self.value)

class ReadonlyAttribute(Attribute):
    pass












